package org.code4everything.wetool.plugin.cmdassist.controller;

import cn.hutool.core.io.FileUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.RuntimeUtil;
import cn.hutool.core.util.StrUtil;
import com.alibaba.fastjson.JSON;
import javafx.fxml.FXML;
import javafx.scene.control.TableColumn;
import javafx.scene.control.TableView;
import javafx.scene.control.TextArea;
import javafx.scene.control.TextField;
import javafx.scene.control.cell.PropertyValueFactory;
import javafx.scene.input.KeyEvent;
import org.code4everything.boot.base.function.VoidFunction;
import org.code4everything.wetool.plugin.cmdassist.constant.AssistConsts;
import org.code4everything.wetool.plugin.cmdassist.model.CmdAssist;
import org.code4everything.wetool.plugin.support.BaseViewController;
import org.code4everything.wetool.plugin.support.control.cell.UnmodifiableTextFieldTableCell;
import org.code4everything.wetool.plugin.support.factory.BeanFactory;
import org.code4everything.wetool.plugin.support.util.FxDialogs;
import org.code4everything.wetool.plugin.support.util.FxUtils;

import java.util.List;
import java.util.regex.Pattern;

/**
 * @author pantao
 * @since 2019/10/8
 */
public class MainController implements BaseViewController, VoidFunction {

    @FXML
    public TextField aliasField;

    @FXML
    public TextField cmdField;

    @FXML
    public TextArea cmdArea;

    @FXML
    public TextField remarkField;

    @FXML
    public TableView<CmdAssist> cmdTable;

    @FXML
    public TableColumn<CmdAssist, String> aliasColumn;

    @FXML
    public TableColumn<CmdAssist, String> remarkColumn;

    @FXML
    public TableColumn<CmdAssist, String> cmdColumn;

    @FXML
    public TextField searchText;

    /**
     * 数据源
     */
    private List<CmdAssist> cmdAssists;

    @FXML
    private void initialize() {
        // 注册
        BeanFactory.registerView(AssistConsts.TAB_ID, AssistConsts.TAB_NAME, this);
        // 设置表格列对应的属性
        aliasColumn.setCellValueFactory(new PropertyValueFactory<>("alias"));
        remarkColumn.setCellValueFactory(new PropertyValueFactory<>("remark"));
        cmdColumn.setCellValueFactory(new PropertyValueFactory<>("cmd"));
        cmdColumn.setCellFactory(UnmodifiableTextFieldTableCell.forTableColumn());
        // 加载配置
        reloadConfig();
    }

    /**
     * 执行命令
     */
    public void exeCmd() {
        String result;
        try {
            result = RuntimeUtil.execForStr(cmdArea.getText());
        } catch (Exception e) {
            FxDialogs.showException("命令运行错误！", e);
            return;
        }
        FxDialogs.showInformation("运行结果：", result);
    }

    public void saveCmd() {
        // 读取预保存的命令
        CmdAssist cmdAssist = new CmdAssist(aliasField.getText(), cmdField.getText(), remarkField.getText());
        // 添加至数据源
        cmdAssists.add(cmdAssist);
        // 添加至表格
        cmdTable.getItems().add(cmdAssist);
        // 保存至文件，并清空文本框
        FileUtil.writeUtf8String(JSON.toJSONString(cmdAssists, true), CmdAssist.getPath());
        FxUtils.clearText(aliasField, cmdField, remarkField);
    }

    /**
     * 打开命令文件，不存在时则创建
     */
    public void openCmdFile() {
        String path = CmdAssist.getPath();
        if (!FileUtil.exist(path)) {
            FileUtil.writeUtf8String("[{}]", path);
        }
        FxUtils.openFile(path);
    }

    /**
     * 读取配置
     */
    public void reloadConfig() {
        cmdTable.getItems().clear();
        cmdAssists = CmdAssist.loadConfig();
        cmdTable.getItems().addAll(cmdAssists);
    }

    public void readCmd() {
        CmdAssist selectedItem = cmdTable.getSelectionModel().getSelectedItem();
        if (ObjectUtil.isNotNull(selectedItem)) {
            cmdArea.setText(selectedItem.getCmd());
        }
    }

    public void search(KeyEvent keyEvent) {
        FxUtils.enterDo(keyEvent, this);
    }

    /**
     * 正则搜索
     */
    @Override
    public void call() {
        String regexp = searchText.getText();
        if (StrUtil.isEmpty(regexp)) {
            cmdTable.getItems().clear();
            cmdTable.getItems().addAll(cmdAssists);
            return;
        }
        Pattern pattern;
        try {
            pattern = Pattern.compile(regexp);
        } catch (Exception e) {
            FxDialogs.showError("正则表达式不正确！");
            return;
        }
        cmdTable.getItems().clear();
        cmdAssists.forEach(ca -> {
            String testStr = ca.getAlias() + ca.getCmd() + ca.getRemark();
            if (pattern.matcher(testStr).find()) {
                cmdTable.getItems().add(ca);
            }
        });
    }
}
